package com.example.service;

import cn.hutool.json.JSONObject;
import com.example.entity.*;
import com.example.entity.others.Test_Map_Question;
import com.example.entity.others.Test_User_Other;
import com.example.entity.others.User_Question;
import com.example.entity.others.User_Subject;
import com.example.mapper.ParentMapper;
import com.example.mapper.QuestionMapper;
import com.example.mapper.StudentMapper;
import com.example.tool.QuestionGenerator;
import org.springframework.stereotype.Service;
import javax.annotation.Resource;
import java.util.*;
import java.util.stream.Collectors;

@Service
public class ParentService {
    @Resource
    public ParentMapper parentMapper;
    @Resource
    public SparkService sparkService;
    @Resource
    public QuestionMapper questionMapper;

    @Resource
    public StudentMapper studentMapper;

    @Resource
    public QuestionGenerator questionGenerator;

    public List<User> listStudent(User user) {
        List<Parent_Student> list = parentMapper.listStudent(user.getUid());
        List<User> users = new ArrayList<>();
        for (Parent_Student parent : list) {
            User student = new User();
            student = parentMapper.getStudentBySid(parent.getSid());
            users.add(student);
        }
        return users;
    }

    public Object bind(Parent_Student parentStudent) {
        int id = parentMapper.getBindbyId(parentStudent);

        if (id == 0){
            parentMapper.bind(parentStudent);
        }
        List<Parent_Student> list = parentMapper.listStudent(parentStudent.getPid());
        List<User> users = new ArrayList<>();
        for (Parent_Student parent : list) {
            User student = new User();
            student = parentMapper.getStudentBySid(parent.getSid());
            users.add(student);
        }
        return users;
    }

    public Object testList(User_Subject userSubject) {
        List<Parent_Student> list = parentMapper.listStudent(userSubject.getUid());
        List<User> users = new ArrayList<>();
        for (Parent_Student parent : list) {
            User student = new User();
            student = parentMapper.getStudentBySid(parent.getSid());
            users.add(student);
        }
        List<JSONObject> tests = new ArrayList<>();
        for (User user : users){
            List<Test_User> testUsers = parentMapper.getTestUserListById(user);
            for (Test_User testUser : testUsers) {
                JSONObject test = new JSONObject();
                test = parentMapper.getTestById(testUser);
                if(test.get("subject") !=null && test.get("uname") !=null){
                    if (userSubject.getSubject() == null && userSubject.getUname() == null){
                        tests.add(test);
                    }else if(userSubject.getSubject() != null && userSubject.getUname() == null){
                        if(String.valueOf(test.get("subject")).equals(userSubject.getSubject())){
                            tests.add(test);
                        }
                    }else if(userSubject.getSubject() == null && userSubject.getUname() != null){
                        if(String.valueOf(test.get("uname")).equals(userSubject.getUname())){
                            tests.add(test);
                        }
                    }else {
                        if( String.valueOf(test.get("uname")).equals(userSubject.getUname()) && String.valueOf(test.get("subject")).equals(userSubject.getSubject())){
                            tests.add(test);
                        }
                    }
                }
            }
        }
        return tests;
    }

    public Object questionAll(Test_User_Other testUserOther) {
        Map<String, List<User_Question>> map = new HashMap<>();

        List<User_Question> userQuestionC = parentMapper.getUqcByTestid(testUserOther.getTest().getTid(), testUserOther.getUser().getUid());
        List<User_Question> userQuestionF = parentMapper.getUqfByTestid(testUserOther.getTest().getTid(), testUserOther.getUser().getUid());
        List<User_Question> userQuestionS = parentMapper.getUqsByTestid(testUserOther.getTest().getTid(), testUserOther.getUser().getUid());

        map.put("选择题", userQuestionC);
        map.put("填空题", userQuestionF);
        map.put("解答题", userQuestionS);

        return map;
    }

    public void createAi(Test_User_Other testUserOther) {
        Test test = testUserOther.getTest();
        User user = testUserOther.getUser();

        Test_User testUser = new Test_User();
        //插入test表
        parentMapper.createTest(test);
        //插入test_user表
        testUser.setTid(test.getTid());
        testUser.setUid(user.getUid());
        parentMapper.createTestUser(testUser);

        Map<String,List<Question>> allMap = questionGenerator.generateQuestionsConcurrently(test,user);

        for (String type : allMap.keySet()){
            List<Question> questionList = allMap.get(type);

            int i = 1;
            for (Question question : questionList){
                if(question.getContent() == null){
                    question.setContent(questionList.get(0).getContent());
                    question.setAnswer(questionList.get(0).getAnswer());
                    question.setKpoint(questionList.get(0).getKpoint());
                }
                question.setQnum(i);
                studentMapper.createQuestion(question);

                Question_Parent questionParent = new Question_Parent();
                questionParent.setQid(question.getQid());
                questionParent.setPid(user.getUid());
                parentMapper.createQuestionParent(questionParent);

                i++;
            }
        }

    }

    public Object humanQuestion(Test_User_Other testUserOther) {
        Test_Map_Question testMapQuestion = new Test_Map_Question();
        Test_User testUser = new Test_User();
        Test test = testUserOther.getTest();
        User user = testUserOther.getUser();

        parentMapper.createTestByHuman(test);

        testUser.setTid(test.getTid());
        testUser.setUid(user.getUid());
        parentMapper.createTestUser(testUser);

        Map<String, List<Question>> map = new HashMap<>();
        List<Question> questionsCAll = new ArrayList<>();
        List<Question> questionFAll = new ArrayList<>();
        List<Question> questionSAll = new ArrayList<>();

        List<Test> tests = parentMapper.getTestBySubject(test);
        for (Test test1 : tests) {
            List<Question> questionsC = parentMapper.getAllCByTid(test1);
            List<Question> questionsF = parentMapper.getAllFByTid(test1);
            List<Question> questionsS = parentMapper.getAllSByTid(test1);

            questionsCAll.addAll(questionsC);
            questionFAll.addAll(questionsF);
            questionSAll.addAll(questionsS);
        }

        map.put("选择题", questionsCAll);
        map.put("填空题", questionFAll);
        map.put("解答题", questionSAll);

        Test test1 = new Test();
        test1.setTid(test.getTid());

        testMapQuestion.setQuestionMap(map);
        testMapQuestion.setTest(test1);
        return testMapQuestion;
    }

    public void createHuman(Test_Map_Question testMapQuestion) {
        Question_Parent questionParent = new Question_Parent();
        Test test = new Test();

        List<Question> questionCAll = testMapQuestion.getQuestionMap().get("选择题");
        List<Question> questionFAll = testMapQuestion.getQuestionMap().get("填空题");
        List<Question> questionSAll = testMapQuestion.getQuestionMap().get("解答题");

        int i = 0;

        questionParent.setPid(testMapQuestion.getUser().getUid());
        test.setTid(testMapQuestion.getTest().getTid());

        for (Question question : questionCAll) {
            i++;
            question.setQnum(i);
            question.setTid(test.getTid());

            parentMapper.createQuestion(question);
            questionParent.setQid(question.getQid());
            parentMapper.createQuestionParent(questionParent);
        }

        test.setCnum(i);
        i = 0;

        for (Question question : questionFAll) {
            i++;
            question.setQnum(i);
            question.setTid(test.getTid());

            parentMapper.createQuestion(question);
            questionParent.setQid(question.getQid());
            parentMapper.createQuestionParent(questionParent);
        }

        test.setFnum(i);
        i = 0;

        for (Question question : questionSAll) {
            i++;
            question.setQnum(i);
            question.setTid(test.getTid());

            parentMapper.createQuestion(question);
            questionParent.setQid(question.getQid());
            parentMapper.createQuestionParent(questionParent);
        }

        test.setSnum(i);

        parentMapper.updateTest(test);
    }

    public Object questionAllParent(Test_User_Other testUserOther) {
        Map<String, List<User_Question>> map = new HashMap<>();

        List<User_Question> userQuestionC = parentMapper.getUqcByTestidParent(testUserOther.getTest().getTid(), testUserOther.getUser().getUid());
        List<User_Question> userQuestionF = parentMapper.getUqfByTestidParent(testUserOther.getTest().getTid(), testUserOther.getUser().getUid());
        List<User_Question> userQuestionS = parentMapper.getUqsByTestidParent(testUserOther.getTest().getTid(), testUserOther.getUser().getUid());

        map.put("选择题", userQuestionC);
        map.put("填空题", userQuestionF);
        map.put("解答题", userQuestionS);

        return map;
    }

    public Object getAnalysis(User_Subject userSubject) {
        List<Parent_Student> list = parentMapper.listStudent(userSubject.getUid());
        List<User> users = new ArrayList<>();
        for (Parent_Student parent : list) {
            User student = new User();
            student = parentMapper.getStudentBySid(parent.getSid());
            users.add(student);
        }
        List<JSONObject> analysisList = new ArrayList<>();
        for (User user : users){
            List<JSONObject> analysisStudents = parentMapper.getAnalysisBySid(user);
            for (JSONObject analysisStudent : analysisStudents) {
                if(analysisStudent.get("subject") !=null && analysisStudent.get("uname") !=null){
                    if (userSubject.getSubject() == null && userSubject.getUname() == null){
                        analysisList.add(analysisStudent);
                    }else if(userSubject.getSubject() != null && userSubject.getUname() == null){
                        if(String.valueOf(analysisStudent.get("subject")).equals(userSubject.getSubject())){
                            analysisList.add(analysisStudent);
                        }
                    }else if(userSubject.getSubject() == null && userSubject.getUname() != null){
                        if(String.valueOf(analysisStudent.get("uname")).equals(userSubject.getUname())){
                            analysisList.add(analysisStudent);
                        }
                    }else {
                        if( String.valueOf(analysisStudent.get("uname")).equals(userSubject.getUname()) && String.valueOf(analysisStudent.get("subject")).equals(userSubject.getSubject())){
                            analysisList.add(analysisStudent);
                        }
                    }
                }
            }
        }
        return analysisList;
    }

    public Object testDelete(Test_User testUser) {
        User user = new User();
        JSONObject json = parentMapper.getTestById(testUser);
        Test test = new Test();
        test.setTid((Integer) json.get("tid"));
        test.setSubject((String) json.get("subject"));
        user.setUid(testUser.getUid());

        parentMapper.deleteTestUser(testUser);
        List<Question> questions = parentMapper.getAllByTid(test);
        for (Question question : questions) {
            Question_Parent questionParent = new Question_Parent();
            questionParent.setQid(question.getQid());
            questionParent.setPid(testUser.getUid());
            parentMapper.deleteQuestion(questionParent);
        }
        User_Subject userSubject = new User_Subject();
        userSubject.setUid(testUser.getUid());
        userSubject.setSubject(test.getSubject());
        return this.testList(userSubject);
    }

    public void doHomework(List<Question_Parent> questionParents) {
        for (Question_Parent qs : questionParents) {
            parentMapper.updateQPById(qs);
        }
    }

    public Object correctingAi(List<User_Question> userQuestions) {
        String input = "";
        int i = 0;
        for (User_Question userQuestion : userQuestions) {
            input = input + "QNum: " + userQuestion.getId() + "\n"
                    + "Question: " + userQuestion.getContent() + "\n"
                    + "Answer: " + userQuestion.getAnswer() + "\n"
                    + "UAnswer: " + userQuestion.getUanswer() + "\n";
            i++;
        }

        List<Question_Parent> questionParents = sparkService.correctParQuestionAi(input, i);
        int pid = userQuestions.get(0).getPid();
        for (Question_Parent questionParent : questionParents) {
            questionParent.setPid(pid);
            parentMapper.updateQSById(questionParent);
        }


        Map<String, List<User_Question>> map = new HashMap<>();

        List<User_Question> userQuestionC = parentMapper.getParUqcByTestid(userQuestions.get(0).getTid(), userQuestions.get(0).getPid());
        List<User_Question> userQuestionF = parentMapper.getParUqfByTestid(userQuestions.get(0).getTid(), userQuestions.get(0).getPid());
        List<User_Question> userQuestionS = parentMapper.getParUqsByTestid(userQuestions.get(0).getTid(), userQuestions.get(0).getPid());


        map.put("选择题", userQuestionC);
        map.put("填空题", userQuestionF);
        map.put("解答题", userQuestionS);

        return map;
    }

    public void questionReset(int tid, int uid) {
        List<Integer> questionId = parentMapper.getQuestionId(tid);
        for (Integer qid : questionId){
            parentMapper.resetQuestion(uid,qid);
        }
    }

    public void setTest(Test_User testUser) {
        Test_User data = parentMapper.getTestUserByTidUid(testUser);
        if(data == null){
            parentMapper.createTestUser(testUser);
            List<Integer> questionList = parentMapper.getQuestionId(testUser.getTid());
            for (Integer id : questionList){
                Question_Student questionStudent = new Question_Student();
                questionStudent.setSid(testUser.getUid());
                questionStudent.setQid(id);
                parentMapper.createQuestionStudent(questionStudent);
            }
        }
    }

    public Object testListParent(User_Subject userSubject) {
        User user = new User();
        user.setUid(userSubject.getUid());
        List<Test_User> testUsers = parentMapper.getTestUserListById(user);
        List<Test> tests = new ArrayList<>();
        for (Test_User testUser : testUsers) {
            Test test = new Test();
            test = parentMapper.getTestByIdParent(testUser);
            if (userSubject.getSubject()==null || test.getSubject().equals(userSubject.getSubject())) {
                tests.add(test);
            }
        }
        return tests;
    }
    public List<JSONObject> studentAnalysis1(User_Subject userSubject) {
        List<Integer> sidList = new ArrayList<>();
        if(userSubject.getSid()!=0){
            sidList.add(userSubject.getSid());
        }else {
            User user = new User();
            user.setUid(userSubject.getUid());
            List<User> userList = this.listStudent(user);
            sidList = userList.stream().map(User::getUid).collect(Collectors.toList());
        }
        return parentMapper.getTidBySid(sidList,userSubject.getSubject());
    }

    public Map<String,List<Object>> studentAnalysis2(User_Subject userSubject) {
        List<Integer> sidList = new ArrayList<>();
        if(userSubject.getSid()!=0){
            sidList.add(userSubject.getSid());
        }else {
            User user = new User();
            user.setUid(userSubject.getUid());
            List<User> userList = this.listStudent(user);
            sidList = userList.stream().map(User::getUid).collect(Collectors.toList());
        }
        List<JSONObject> list = parentMapper.getStudentAnalysis2(sidList,userSubject.getSubject());
        List<Object> kPointList = list.stream().map(x -> x.get("kpoint")).collect(Collectors.toList());
        List<Object> incorrectCountList = list.stream().map(x -> x.get("incorrect_count")).collect(Collectors.toList());
        List<Object> correctCountList = list.stream().map(x -> x.get("correct_count")).collect(Collectors.toList());
        Map<String,List<Object>> listMap = new HashMap<>();
        listMap.put("kPoint",kPointList);
        listMap.put("incorrectCount",incorrectCountList);
        listMap.put("correctCount",correctCountList);
        return listMap;
    }


    public Map<String, List<Object>> studentAnalysis3(User_Subject userSubject) {
        List<Integer> sidList = new ArrayList<>();
        if(userSubject.getSid()!=0){
            sidList.add(userSubject.getSid());
        }else {
            User user = new User();
            user.setUid(userSubject.getUid());
            List<User> userList = this.listStudent(user);
            sidList = userList.stream().map(User::getUid).collect(Collectors.toList());
        }
        List<String> list = parentMapper.getKnPoint(sidList,userSubject.getSubject());
        Map<String,List<Object>> listMap = new HashMap<>();
        for(String knPoint : list){
            List<Object> result = new ArrayList<>();
            List<Integer> tidList = new ArrayList<>();
            tidList = parentMapper.getStudentAnalysis3(knPoint,sidList,userSubject.getSubject());
            for (Integer tid : tidList){
                Object num = new Object();
                num = parentMapper.getStudentAnalysis31(tid,sidList);
                result.add(num);
            }
            listMap.put(knPoint,result);
        }
        return listMap;
    }

    public Map<String, List<Object>> studentAnalysis4(User_Subject userSubject) {
        List<Integer> sidList = new ArrayList<>();
        if(userSubject.getSid()!=0){
            sidList.add(userSubject.getSid());
        }else {
            User user = new User();
            user.setUid(userSubject.getUid());
            List<User> userList = this.listStudent(user);
            sidList = userList.stream().map(User::getUid).collect(Collectors.toList());
        }
        List<JSONObject> list = parentMapper.getStudentAnalysis4(sidList,userSubject.getSubject());
        List<Object> kPointList = list.stream().map(x -> x.get("kpoint")).collect(Collectors.toList());
        List<Object> incorrectCountList = list.stream().map(x -> x.get("result")).collect(Collectors.toList());
        Map<String,List<Object>> listMap = new HashMap<>();
        listMap.put("kPoint",kPointList);
        listMap.put("result",incorrectCountList);
        return listMap;
    }
}
